﻿using Application.Instock_hService;
using Domain.Entity.In;
using Domain.Entity;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Caching.Distributed;
using System.Text.Json;
using Domain.Entity.ord;
using Application.Purchase_hService;
using Application.Purchase_dService;
using Application.ProductService;
using Application.StockService;
using Application.PublicFileService;
using Application.Instock_dService;
using System.Transactions;
using Application.CodeRuleService;
using Application.ISale_hService;
using Application.Sale_dService;
using Application.SaleReturn_dService;
using Application.SaleReturn_hService;
using Domain.Entity.search;
using Domain.Entity.zct;
using OfficeOpenXml.FormulaParsing.Excel.Functions.Math;
using System.Runtime.Intrinsics.Arm;
using WMSManage.Filter;
using Application.Check_hService;
using Application.Check_dService;
using Application.Allot_hService;
using Application.Allot_dService;

namespace WMSManage.Controllers
{
    [Route("api/[controller]/[action]")]
    [ApiController]
    [Authorize]//需要鉴权
    public class Instock_hController : ControllerBase
    {
        private readonly IInstock_hService instock_HService;
        private readonly IDistributedCache distributedCache;
        private readonly IPurchase_hService purchase_HService;
        private readonly IPurchase_dService purchase_DService;
        private readonly IProductService productService;
        private readonly IStockService stockService;
        private readonly IPublicFileService publicFileService;
        private readonly IInstock_dService instock_DService;
        private readonly ICodeRuleService codeRuleService;
        private readonly ISaleReturn_hService saleReturn_HService;
        private readonly ISaleReturn_dService saleReturn_DService;
        private readonly ISale_hService sale_HService;
        private readonly ISale_dService sale_DService;
        private readonly ICheck_hService check_HService;
        private readonly ICheck_dService check_DService;
        private readonly IAllot_hService allot_HService;
        private readonly IAllot_dService allot_DService;

        public Instock_hController(IInstock_hService instock_HService,IDistributedCache distributedCache, IPurchase_hService purchase_HService,IPurchase_dService purchase_DService,IProductService productService,IStockService stockService,IPublicFileService publicFileService,IInstock_dService instock_DService,ICodeRuleService codeRuleService,
                                   ISaleReturn_hService saleReturn_HService,ISaleReturn_dService saleReturn_DService,ISale_hService sale_HService,ISale_dService sale_DService,ICheck_hService check_HService,ICheck_dService check_DService,IAllot_hService allot_HService,IAllot_dService allot_DService)
        {
            this.instock_HService = instock_HService;
            this.distributedCache = distributedCache;
            this.purchase_HService = purchase_HService;
            this.purchase_DService = purchase_DService;
            this.productService = productService;
            this.stockService = stockService;
            this.publicFileService = publicFileService;
            this.instock_DService = instock_DService;
            this.codeRuleService = codeRuleService;
            this.saleReturn_HService = saleReturn_HService;
            this.saleReturn_DService = saleReturn_DService;
            this.sale_HService = sale_HService;
            this.sale_DService = sale_DService;
            this.check_HService = check_HService;
            this.check_DService = check_DService;
            this.allot_HService = allot_HService;
            this.allot_DService = allot_DService;
        }


        /// <summary>
        /// 分页查询入库单
        /// </summary>
        /// <param name="code"></param>
        /// <param name="type"></param>
        /// <param name="status"></param>
        /// <param name="whid"></param>
        /// <param name="CurrentPage"></param>
        /// <returns></returns>
        [HttpGet]
        public async Task<FenYe<Instock_h>> GetInstock_h(string? code, string? type, int? status, int? whid,int CurrentPage)
        {
            FenYe<Instock_h> fenYe = new FenYe<Instock_h>()
            {
                CurrentPage = CurrentPage,
            };
            return await instock_HService.GetInstock_h(fenYe, code, type, status, whid);
        }


        /// <summary>
        /// 刷新缓存
        /// </summary>
        /// <param name="code"></param>
        /// <param name="type"></param>
        /// <param name="status"></param>
        /// <param name="whid"></param>
        /// <param name="CurrentPage"></param>
        /// <returns></returns>
        [HttpGet]
        public IActionResult Refresh(string? code, string? type, int? status, int? whid, int CurrentPage)
        {
            //缓存键
            string key = "Instock_h" + code + type + whid + status + CurrentPage;

            // 清除缓存键
            distributedCache.Remove(key);

            // 返回成功消息
            return Ok(new { success = true, message = "ok" });
        }


        /// <summary>
        /// 高级查询
        /// </summary>
        /// <param name="code"></param>
        /// <param name="starttotal"></param>
        /// <param name="endtotal"></param>
        /// <param name="startdate"></param>
        /// <param name="enddate"></param>
        /// <param name="startnum"></param>
        /// <param name="endnum"></param>
        /// <param name="status"></param>
        /// <param name="type"></param>
        /// <param name="whid"></param>
        /// <param name="createname"></param>
        /// <param name="startcreatetime"></param>
        /// <param name="endcreatetime"></param>
        /// <param name="approvername"></param>
        /// <param name="startapprovertime"></param>
        /// <param name="endapprovertime"></param>
        /// <param name="inuser"></param>
        /// <param name="inorder"></param>
        /// <param name="CurrentPage"></param>
        /// <returns></returns>
        [HttpGet]
        public async Task<FenYe<Instock_h>> GetAdvancedInstock_h(string? code, string? starttotal, string? endtotal, string? startdate, string? enddate, string? startnum, string? endnum, int? status, string? type, int? whid, string? createname, string? startcreatetime, string? endcreatetime, string? approvername, string? startapprovertime, string? endapprovertime, string? inuser, string? inorder,int CurrentPage)
        {
            FenYe<Instock_h> fenYe = new FenYe<Instock_h>()
            {
                CurrentPage = CurrentPage,
            };
            return await instock_HService.GetAdvancedInstock_h(fenYe, code, starttotal, endtotal, startdate, enddate, startnum, endnum, status, type, whid, createname, startcreatetime, endcreatetime, approvername, startapprovertime, endapprovertime, inuser, inorder);
        }


        ///// <summary>
        ///// 添加入库单
        ///// </summary>
        ///// <param name="addInstock_HDto"></param>
        ///// <returns></returns>
        //[HttpPost]
        //public async Task<int> AddInstock_h(AddInstock_hDto addInstock_HDto)
        //{
        //    return await instock_HService.AddInstock_h(addInstock_HDto);
        //}



        /// <summary>
        /// 入库（创建单据，不影响库存）
        /// </summary>
        /// <param name="payload"></param>
        /// <returns></returns>
        [HttpPost]
        public async Task<int> AddInstock_h(AddInstockPayload payload)
        {
            //开启事务
            using var scope = new TransactionScope(TransactionScopeAsyncFlowOption.Enabled);
            try
            {
                //业务逻辑
                //1.添加主入库单
                var id = await instock_HService.AddInstock_h(payload.instockData);//返回的是当前主键

                //2.添加入库明细
                foreach (var details in payload.instockDetails)
                {
                    var instock_d = new AddInstock_dDto
                    {
                        in_id = id,
                        proc_id = details.proc_id,
                        proc_name = details.proc_name,
                        slot_id = details.slot_id,
                        slot_name = details.slot_name,
                        ind_numtotal = details.ind_numtotal,
                        ind_price = details.ind_price,
                        ind_num = details.ind_num,
                        ind_instockOK_num = details.ind_instockOK_num,
                        ind_instockNO_num = details.ind_instockNO_num,
                        ind_total = details.ind_total,
                        proc_date = details.proc_date,
                        remark = details.remark,
                    };
                    await instock_DService.AddInstock_d(instock_d);
                }

                //3.添加附件
                foreach (var item in payload.attachments)
                {
                    await publicFileService.AddFile(item);
                }
                scope.Complete();//提交事务
                return id; // 返回主入库单ID表示成功
            }
            catch (Exception ex)
            {
                //出错自动回滚
                Console.WriteLine(ex.Message);
                return 0;
            }
        }

        /// <summary>
        /// 入库统计
        /// </summary>
        /// <param name="timeType"></param>
        /// <param name="code"></param>
        /// <param name="whid"></param>
        /// <param name="instarttime"></param>
        /// <param name="inendtime"></param>
        /// <param name="starttime"></param>
        /// <param name="endtime"></param>
        /// <param name="inType"></param>
        /// <param name="page"></param>
        /// <param name="pagesize"></param>
        /// <returns></returns>
        [HttpGet]
        public async Task<Instock_hTJResult> Instock_hTJ(string? timeType, string? code, int? whid, string? instarttime, string? inendtime, string? starttime, string? endtime, string inType, int? page, int? pagesize)
        {
            //缓存键
            string key = "Instock_hTJResult" + timeType + code + whid + instarttime + inendtime + starttime + endtime + inType  + page + pagesize;
            //从缓存中获取数据
            var data = await distributedCache.GetStringAsync(key);
            if (data != null)
            {
                //从缓存中查
                return JsonSerializer.Deserialize<Instock_hTJResult>(data);
            }
            //从数据库查
            var result = await instock_HService.Instock_hTJ(timeType, code, whid, instarttime, inendtime, starttime, endtime, inType, page, pagesize);
            //将查询到的结果存入缓存
            if (result != null)
            {
                var option = new DistributedCacheEntryOptions
                {
                    AbsoluteExpirationRelativeToNow = TimeSpan.FromMinutes(10)//10分钟
                };
                await distributedCache.SetStringAsync(key, JsonSerializer.Serialize(result), option);
            }
            return result;
        }


        /// <summary>
        /// 入库审核（影响库存，货品，对应单据）
        /// </summary>
        /// <param name="instockid"></param>
        /// <param name="status"></param>
        /// <param name="approvername"></param>
        /// <param name="approvertime"></param>
        /// <returns></returns>
        [HttpPut]
        public async Task<int> ApproverInstock_h(int instockid, int status, string approvername, string approvertime)
        {
            if (status == 3)//如果是驳回
            {
                //只改变状态
                return await instock_HService.UpdateStatus(instockid, status, approvername, approvertime);
            }

            //通过的话对库存，货品，对应单据，明细做出操作
            //开启事务
            using var scope = new TransactionScope(TransactionScopeAsyncFlowOption.Enabled);
            try
            {
                //获取入库单及明细
                var instockHeader = await instock_HService.GetInstock_hById(instockid);
                var instockDetails = await instock_DService.GetInstock_Ds(instockid);

                //=====根据入库类型执行不同业务逻辑
                if (instockHeader.in_type == "进货入库")
                {
                    // 获取采购单信息
                    var purchase_h = await purchase_HService.Getid(instockHeader.in_order);

                    // 安全计算：防止入库总量超过采购量
                    int maxAllowOK = (int)(purchase_h.pur_num - purchase_h.pur_instockOK_num);
                    int actualOK = Math.Min((int)instockHeader.in_instockOK_num, maxAllowOK);
                    int actualNO = (int)instockHeader.in_instockOK_num - actualOK;

                    // 更新采购单主表
                    var updateh = new UpdatehNum
                    {
                        pur_id = purchase_h.pur_id,
                        pur_instockOK_num = purchase_h.pur_instockOK_num + actualOK,
                        pur_instockNO_num = purchase_h.pur_instockNO_num + actualNO,
                        pur_status = (purchase_h.pur_instockOK_num + actualOK) < purchase_h.pur_num ? 5 : 6
                    };
                    await purchase_HService.Updatenum(updateh);

                    // 更新采购单明细
                    foreach (var detail in instockDetails)
                    {
                        var purdid = await purchase_DService.Getid(updateh.pur_id, detail.proc_id);
                        var updated = new UpdatedNum
                        {
                            purd_id = purdid,
                            purd_instockOK_num = detail.ind_instockOK_num,
                            purd_instockNo_num = detail.ind_instockNO_num
                        };
                        await purchase_DService.Updatenum(updated);
                    }

                    // 进货入库的库存更新逻辑
                    foreach (var detail in instockDetails)
                    {
                        var updateinventoryDto = new UpdateinventoryDto
                        {
                            proc_id = detail.proc_id,
                            proc_inventory = detail.ind_num, // 增加总库存
                            proc_ky_inventory = 0, // 增加可用库存
                            proc_inventory_money = detail.ind_total
                        };
                        await productService.Updateinventory(updateinventoryDto);
                    }

                    // 更新仓位库存
                    foreach (var detail in instockDetails)
                    {
                        var stock = new AddStockDto
                        {
                            stk_code = await codeRuleService.GeneratedCode(18),
                            wh_id = (int)instockHeader.wh_id,
                            slot_id = detail.slot_id,
                            proc_id = detail.proc_id,
                            stk_hand_num = (int)detail.ind_num,
                            stk_price = (double)detail.ind_price,
                            stk_total = detail.ind_total,
                            remark = detail.remark
                        };

                        var stockdata = await stockService.GetStockByCriteria(stock.proc_id, stock.wh_id, stock.slot_id);
                        if (stockdata == null)
                        {
                            // 没有就添加
                            await stockService.AddStock(stock);
                        }
                        else
                        {
                            // 有就更新，加权平均计算单价
                            double price = Math.Round((stockdata.stk_total + stock.stk_total) / (stockdata.stk_hand_num + stock.stk_hand_num), 2);
                            stock.stk_price = price;
                            await stockService.UpdateStock(stock);
                        }
                    }
                }
                else if (instockHeader.in_type == "退货入库")
                {
                    // --- 1. 获取关联的销售退货单 ---
                    var saleReturn_h = await saleReturn_HService.GetSaleReturn_hByCode(instockHeader.in_order);
                    if (saleReturn_h == null) throw new Exception("未找到关联的销售退货单: " + instockHeader.in_order);

                    var sale_h = await sale_HService.GetSale_HById(saleReturn_h.sale_id);
                    if (sale_h == null) throw new Exception("未找到销售退货单关联的原始销售单");

                    // --- 2. 更新销售退货单主表 ---
                    int maxAllowOK_sret = (int)(saleReturn_h.salet_num - saleReturn_h.salet_instockOK_num);
                    int actualOK_sret = Math.Min((int)instockHeader.in_instockOK_num, maxAllowOK_sret);
                    int actualNO_sret = (int)instockHeader.in_instockOK_num - actualOK_sret;
                    int sretid = saleReturn_h.salet_id;
                    int oknum_sret = (int)(saleReturn_h.salet_instockOK_num + actualOK_sret);
                    int nonum_sret = (int)(saleReturn_h.salet_instockNO_num + actualNO_sret);
                    int statu_sret = oknum_sret >= saleReturn_h.salet_num ? 6 : 5; // 6:全部入库, 5:部分入库
                    await saleReturn_HService.UpdateNum(sretid, oknum_sret, nonum_sret, statu_sret);

                    // --- 3. 更新原始销售单主表 ---
                    int saleid = sale_h.sale_id;
                    int returnnum_sale = (int)(sale_h.sale_returned_num + actualOK_sret);
                    int rstatu_sale = returnnum_sale >= sale_h.sale_num ? 11 : 10; // 11:全部退货, 10:部分退货
                    await sale_HService.UpdateRNum(saleid, returnnum_sale, rstatu_sale);

                    // --- 4. 一次性获取所有销售明细，用于后续查找 ---
                    var allSaleDetails = await sale_DService.GetSale_ds(saleid);
                    if (allSaleDetails == null || !allSaleDetails.Any())
                    {
                        throw new Exception("未能获取到原始销售单的任何明细项。");
                    }

                    // --- 5. 循环处理每一条入库明细 ---
                    foreach (var detail in instockDetails)
                    {
                        var sale_d_item = allSaleDetails.FirstOrDefault(sd => sd.proc_id == detail.proc_id);
                        if (sale_d_item == null)
                        {
                            Console.WriteLine($"警告：在原始销售单 {sale_h.sale_code} 中未找到货品ID为 {detail.proc_id} 的明细项。");
                            continue;
                        }

                        // 计算本次应增加到【物理库存】的数量
                        int totalOutstockedQty = (int)sale_d_item.saled_outstockOK_num; // 这批货总共出库了多少
                        int previouslyReturnedQty = (int)sale_d_item.saled_returned_num; // 这批货之前已经退了多少
                        int maxStockAddition = totalOutstockedQty - previouslyReturnedQty; // 本次最多能入库多少
                        if (maxStockAddition < 0) maxStockAddition = 0;

                        int inventoryAdditionQty = Math.Min((int)detail.ind_num, maxStockAddition);

                        // --- 6. 仅当实际需要增加库存时，才执行库存操作 ---
                        if (inventoryAdditionQty > 0)
                        {
                            var updateinventoryDto = new UpdateinventoryDto
                            {
                                proc_id = detail.proc_id,
                                proc_inventory = inventoryAdditionQty, // 增加总库存
                                proc_ky_inventory = 0, // 可用库存不增加，因为退货时已经预留了
                                proc_inventory_money = detail.ind_price * inventoryAdditionQty
                            };
                            await productService.Updateinventory(updateinventoryDto);

                            var stock = new AddStockDto
                            {
                                wh_id = (int)instockHeader.wh_id,
                                slot_id = detail.slot_id,
                                proc_id = detail.proc_id,
                                stk_hand_num = inventoryAdditionQty,
                                stk_total = (double)(detail.ind_price * inventoryAdditionQty),
                                remark = detail.remark
                            };

                            var stockdata = await stockService.GetStockByCriteria(stock.proc_id, stock.wh_id, stock.slot_id);
                            if (stockdata != null)
                            {
                                // 加权平均计算单价
                                double newTotalQty = stockdata.stk_hand_num + stock.stk_hand_num;
                                double newTotalValue = stockdata.stk_total + stock.stk_total;
                                double price = Math.Round(newTotalValue / newTotalQty, 2);
                                stock.stk_price = double.IsNaN(price) ? 0 : price;
                                await stockService.UpdateStock(stock);
                            }
                            else
                            {
                                // 如果没有现有库存，直接添加
                                await stockService.AddStock(stock);
                            }
                        }

                        // --- 7. 更新关联单据的明细状态 ---
                        var sretdid = await saleReturn_DService.Getid(sretid, detail.proc_id);
                        await saleReturn_DService.UpdateNum(sretdid, detail.ind_instockOK_num, detail.ind_instockNO_num);

                        // 更新原始销售单明细的已退货数量
                        await sale_DService.UpdateRNum(sale_d_item.saled_id, detail.ind_instockOK_num);
                    }
                }
                else if (instockHeader.in_type == "期初入库")
                {
                    // 期初入库的库存更新逻辑
                    foreach (var detail in instockDetails)
                    {
                        var updateinventoryDto = new UpdateinventoryDto
                        {
                            proc_id = detail.proc_id,
                            proc_inventory = detail.ind_num, // 本次入库的数量
                            proc_ky_inventory = detail.ind_num, // 期初入库时可用库存等于总库存
                            proc_inventory_money = detail.ind_total
                        };
                        await productService.Updateinventory(updateinventoryDto);
                    }

                    // 更新仓位库存
                    foreach (var detail in instockDetails)
                    {
                        var stock = new AddStockDto
                        {
                            stk_code = await codeRuleService.GeneratedCode(18),
                            wh_id = (int)instockHeader.wh_id,
                            slot_id = detail.slot_id,
                            proc_id = detail.proc_id,
                            stk_hand_num = (int)detail.ind_num,
                            stk_price = (double)detail.ind_price,
                            stk_total = detail.ind_total,
                            remark = detail.remark
                        };

                        var stockdata = await stockService.GetStockByCriteria(stock.proc_id, stock.wh_id, stock.slot_id);
                        if (stockdata == null)
                        {
                            // 没有就添加
                            await stockService.AddStock(stock);
                        }
                        else
                        {
                            // 有就更新，加权平均计算单价
                            double price = Math.Round((stockdata.stk_total + stock.stk_total) / (stockdata.stk_hand_num + stock.stk_hand_num), 2);
                            stock.stk_price = price;
                            await stockService.UpdateStock(stock);
                        }
                    }
                }
                else if (instockHeader.in_type == "盘盈入库")
                {
                    // 库存更新逻辑
                    foreach (var detail in instockDetails)
                    {
                        var updateinventoryDto = new UpdateinventoryDto
                        {
                            proc_id = detail.proc_id,
                            proc_inventory = detail.ind_num, // 本次入库的数量
                            proc_ky_inventory = detail.ind_num, // 期初入库时可用库存等于总库存
                            proc_inventory_money = detail.ind_total
                        };
                        await productService.Updateinventory(updateinventoryDto);
                    }

                    // 更新仓位库存
                    foreach (var detail in instockDetails)
                    {
                        var stock = new AddStockDto
                        {
                            stk_code = await codeRuleService.GeneratedCode(18),
                            wh_id = (int)instockHeader.wh_id,
                            slot_id = detail.slot_id,
                            proc_id = detail.proc_id,
                            stk_hand_num = (int)detail.ind_num,
                            stk_price = (double)detail.ind_price,
                            stk_total = detail.ind_total,
                            remark = detail.remark
                        };

                        var stockdata = await stockService.GetStockByCriteria(stock.proc_id, stock.wh_id, stock.slot_id);
                        if (stockdata == null)
                        {
                            // 没有就添加
                            await stockService.AddStock(stock);
                        }
                        else
                        {
                            // 有就更新，加权平均计算单价
                            double price = Math.Round((stockdata.stk_total + stock.stk_total) / (stockdata.stk_hand_num + stock.stk_hand_num), 2);
                            stock.stk_price = price;
                            await stockService.UpdateStock(stock);
                        }
                    }

                    //将修改盘点主单和盘点明细单的入库状态（5：部分入库，6：已完成）
                    if (!string.IsNullOrEmpty(instockHeader.in_order))
                    {
                        //获取关联的盘点单ID
                        int icid=await check_HService.Getid(instockHeader.in_order);
                        //名称
                        string name = "instock_status";
                        //更新盘点单的入库状态
                        await check_HService.UpdateStatus(name, 6,icid);
                        foreach (var detail in instockDetails)
                        {
                            await check_DService.UpdateStatus(name, 6, icid,detail.proc_id);
                        }
                    }
                }
                else if (instockHeader.in_type == "调拨入库")
                {
                    // 更新仓位库存
                    foreach (var detail in instockDetails)
                    {
                        var stock = new AddStockDto
                        {
                            stk_code = await codeRuleService.GeneratedCode(18),
                            wh_id = (int)instockHeader.wh_id,
                            slot_id = detail.slot_id,
                            proc_id = detail.proc_id,
                            stk_hand_num = (int)detail.ind_num,
                            stk_price = (double)detail.ind_price,
                            stk_total = detail.ind_total,
                            remark = detail.remark
                        };

                        var stockdata = await stockService.GetStockByCriteria(stock.proc_id, stock.wh_id, stock.slot_id);
                        if (stockdata == null)
                        {
                            // 没有就添加
                            await stockService.AddStock(stock);
                        }
                        else
                        {
                            // 有就更新，加权平均计算单价
                            double price = Math.Round((stockdata.stk_total + stock.stk_total) / (stockdata.stk_hand_num + stock.stk_hand_num), 2);
                            stock.stk_price = price;
                            await stockService.UpdateStock(stock);
                        }
                    }

                    //将修改调拨单的入库状态
                    if (!string.IsNullOrEmpty(instockHeader.in_order))
                    {
                        //获取关联的调拨单ID
                        int alid = await allot_HService.Getid(instockHeader.in_order);
                        //名称
                        string name = "instock_status";
                        string nameok = "al_instockOK_num";
                        string nameno = "al_instockNO_num";
                        string nameokd = "ald_instockOK_num";
                        string namenod = "ald_instockNO_num";
                        //更新盘点单的入库状态
                        await allot_HService.UpdateStatus(nameok, (int)instockHeader.in_instockOK_num, nameno, (int)instockHeader.in_instockNO_num, name, alid);
                        foreach (var detail in instockDetails)
                        {
                            await allot_DService.UpdateStatus(nameokd, (int)detail.ind_instockOK_num, namenod, (int)detail.ind_instockNO_num, name, alid,detail.proc_id);
                        }
                    }
                }

                //修改状态
                await instock_HService.UpdateStatus(instockid, status, approvername, approvertime);

                scope.Complete();//提交事务
                return 1;
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex.Message);
                return 0;
            }
        }


        /// <summary>
        /// 根据id查询入库单
        /// </summary>
        /// <param name="instockid"></param>
        /// <returns></returns>
        [HttpGet]
        public async Task<Instock_h> GetInstock_hById(int instockid)
        {
            return await instock_HService.GetInstock_hById(instockid);
        }



        /// <summary>
        /// 修改入库单(不影响库存)
        /// </summary>
        /// <param name="updateInstockPayload"></param>
        /// <returns></returns>
        [HttpPost]
        public async Task<int> UpdateInstock_h(UpdateInstockPayload updateInstockPayload)
        {
            //开启事务
            using var scope = new TransactionScope(TransactionScopeAsyncFlowOption.Enabled);
            try
            {
                //1.修改主入库单
                await instock_HService.UpdateInstock_h(updateInstockPayload.instockData);

                //2.修改入库明细
                //2.1获取所有旧明细
                var oldDetails = await instock_DService.GetInstock_Ds(updateInstockPayload.instockData.in_id);
                var oldDetailsIds = oldDetails.Select(d => d.ind_id).ToList();//所有旧明细的主键id
                //2.2从前端提交的数据中获取到新的明细
                var newDetails=updateInstockPayload.instockDetails;
                var newDetailsIds = newDetails.Where(d => d.ind_id > 0).Select(d => d.ind_id).ToList();//所有新明细的主键id
                //2.3新id和旧id看久id有没有多出来的有的话就删除
                var idsToDelete=oldDetailsIds.Except(newDetailsIds).ToList();
                if(idsToDelete.Any())
                {
                    foreach (var id in idsToDelete)
                    {
                        //删掉
                        await instock_DService.DeleteInstock_d(id);
                    }
                }
                //2.4遍历所有明细,进行新增或修改
                var detailsToAdd = new List<AddInstock_dDto>();
                var detailsToUpdate = new List<AddInstock_dDto>();
                foreach (var detail in updateInstockPayload.instockDetails)
                {
                    if (detail.ind_id > 0)
                    {
                        detailsToUpdate.Add(detail);//改
                    }
                    else
                    {
                        detail.in_id = updateInstockPayload.instockData.in_id;
                        detailsToAdd.Add(detail);//增
                    }
                }
                if(detailsToUpdate.Any())
                {
                    foreach (var item in detailsToUpdate)
                    {
                        await instock_DService.UpdateInstock_d(item);
                    }
                }
                if (detailsToAdd.Any())
                {
                    foreach (var item in detailsToAdd)
                    {
                        await instock_DService.AddInstock_d(item);
                    }
                }


                //3.修改附件
                //获取附件
                var filelist = updateInstockPayload.attachments;
                //先删除
                foreach (var item in filelist)
                {
                    await publicFileService.DeleteFile(item.business_type, item.business_code);
                }
                //在添加
                foreach (var item in filelist)
                {
                    await publicFileService.AddFile(item);
                }
                scope.Complete();//提交事务
                return 1;
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex.Message);
                return 0;
            }
        }


        /// <summary>
        /// 删除入库单
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        [HttpPut]
        public async Task<int> DeleteInstock_h(int id)
        {
            return await instock_HService.DeleteInstock_h(id);
        }


        /// <summary>
        /// 修改单据状态
        /// </summary>
        /// <param name="instockid"></param>
        /// <param name="status"></param>
        /// <param name="approvername"></param>
        /// <param name="approvertime"></param>
        /// <returns></returns>
        [HttpPut]
        public async Task<int> UpdateStatus(int instockid, int status)
        {
            return await instock_HService.UpdateStatus(instockid, status);
        }



        /// <summary>
        /// 根据货品id查询入库记录
        /// </summary>
        /// <param name="procid"></param>
        /// <returns></returns>
        [HttpGet]
        public async Task<List<Instock_h>> GetAllInstock_h(int procid)
        {
            return await instock_HService.GetAllInstock_h(procid);
        }


        /// <summary>
        /// 根据关联单号查询入库记录
        /// </summary>
        /// <param name="code"></param>
        /// <returns></returns>
        [HttpGet]
        public async Task<List<Instock_h>> GetAllInstock_hByCode(string code)
        {
            return await instock_HService.GetAllInstock_hByCode(code);
        }

        /// <summary>
        /// 通过供应商ID查
        /// </summary>
        /// <param name="CurrentPage"></param>
        /// <param name="sup_id"></param>
        /// <returns></returns>
        [HttpGet]
        public async Task<FenYe<Instock_h>> GetInstock_hSup(int CurrentPage, int sup_id)
        {

            FenYe<Instock_h> fenYe = new FenYe<Instock_h>()
            {
                CurrentPage = CurrentPage,
            };
            return await instock_HService.GetInstock_hSup(fenYe, sup_id);
        }

        /// <summary>
        /// 通过客户ID查
        /// </summary>
        /// <param name="CurrentPage"></param>
        /// <param name="cust_id"></param>
        /// <returns></returns>
        [HttpGet]
        public async Task<FenYe<Instock_h>> GetInstock_hCust(int CurrentPage, int cust_id)
        {

            FenYe<Instock_h> fenYe = new FenYe<Instock_h>()
            {
                CurrentPage = CurrentPage,
            };
            return await instock_HService.GetInstock_hCust(fenYe, cust_id);
        }
    }
}
